﻿using System;
using System.Collections.Generic;
using System.Text;

namespace NFixedPoint.LookupTable
{
    internal class TanLookupTable
    {
        public static long Tan(long numRaw)
        {
            var sign = 1;
            if (numRaw < 0)
            {
                numRaw = -numRaw;
                sign = -1;
            }

            var index = (int)(numRaw >> (FixedPoint.PRECISION - 9));
            var fraction = (numRaw - (index << (FixedPoint.PRECISION - 9))) << 9;
            var a = TanLut[index];
            var b = TanLut[index + 1];
            var v2 = a + (((b - a) * fraction) >> FixedPoint.PRECISION);
            return v2 * sign;
        }
        public static readonly int[] TanLut = {
            0, 804, 1609, 2414, 3220, 4026, 4834, 5644, 6455, 7268,
            8083, 8901, 9721, 10545, 11372, 12202, 13036, 13874, 14717, 15564,
            16416, 17273, 18136, 19005, 19880, 20762, 21650, 22546, 23449, 24360,
            25280, 26208, 27146, 28093, 29050, 30018, 30996, 31986, 32988, 34002,
            35030, 36071, 37126, 38196, 39281, 40382, 41500, 42636, 43790, 44963,
            46156, 47369, 48605, 49863, 51145, 52451, 53784, 55144, 56532, 57950,
            59398, 60880, 62395, 63947, 65536, 67165, 68835, 70548, 72308, 74116,
            75974, 77887, 79856, 81885, 83977, 86135, 88365, 90670, 93054, 95523,
            98082, 100736, 103493, 106358, 109340, 112447, 115687, 119071, 122609, 126314,
            130198, 134276, 138564, 143081, 147847, 152884, 158218, 163878, 169896, 176309,
            183161, 190499, 198380, 206870, 216043, 225990, 236817, 248648, 261634, 275959,
            291845, 309568, 329472, 351993, 377693, 407305, 441808, 482534, 531352, 590958,
            665398, 761030, 888450, 1066730, 1334016, 1779314, 2669641, 5340086, -2147483648, -5340086,
            -2669641, -1779314, -1334016, -1066730, -888450, -761030, -665398, -590958, -531352, -482534,
            -441808, -407305, -377693, -351993, -329472, -309568, -291845, -275959, -261634, -248648,
            -236817, -225990, -216043, -206870, -198380, -190499, -183161, -176309, -169896, -163878,
            -158218, -152884, -147847, -143081, -138564, -134276, -130198, -126314, -122609, -119071,
            -115687, -112447, -109340, -106358, -103493, -100736, -98082, -95523, -93054, -90670,
            -88365, -86135, -83977, -81885, -79856, -77887, -75974, -74116, -72308, -70548,
            -68835, -67165, -65536, -63947, -62395, -60880, -59398, -57950, -56532, -55144,
            -53784, -52451, -51145, -49863, -48605, -47369, -46156, -44963, -43790, -42636,
            -41500, -40382, -39281, -38196, -37126, -36071, -35030, -34002, -32988, -31986,
            -30996, -30018, -29050, -28093, -27146, -26208, -25280, -24360, -23449, -22546,
            -21650, -20762, -19880, -19005, -18136, -17273, -16416, -15564, -14717, -13874,
            -13036, -12202, -11372, -10545, -9721, -8901, -8083, -7268, -6455, -5644,
            -4834, -4026, -3220, -2414, -1609, -804, 0, 804, 1609, 2414,
            3220, 4026, 4834, 5644, 6455, 7268, 8083, 8901, 9721, 10545,
            11372, 12202, 13036, 13874, 14717, 15564, 16416, 17273, 18136, 19005,
            19880, 20762, 21650, 22546, 23449, 24360, 25280, 26208, 27146, 28093,
            29050, 30018, 30996, 31986, 32988, 34002, 35030, 36071, 37126, 38196,
            39281, 40382, 41500, 42636, 43790, 44963, 46156, 47369, 48605, 49863,
            51145, 52451, 53784, 55144, 56532, 57950, 59398, 60880, 62395, 63947,
            65536, 67165, 68835, 70548, 72308, 74116, 75974, 77887, 79856, 81885,
            83977, 86135, 88365, 90670, 93054, 95523, 98082, 100736, 103493, 106358,
            109340, 112447, 115687, 119071, 122609, 126314, 130198, 134276, 138564, 143081,
            147847, 152884, 158218, 163878, 169896, 176309, 183161, 190499, 198380, 206870,
            216043, 225990, 236817, 248648, 261634, 275959, 291845, 309568, 329472, 351993,
            377693, 407305, 441808, 482534, 531352, 590958, 665398, 761030, 888450, 1066730,
            1334016, 1779314, 2669641, 5340086, -2147483648, -5340086, -2669641, -1779314, -1334016, -1066730,
            -888450, -761030, -665398, -590958, -531352, -482534, -441808, -407305, -377693, -351993,
            -329472, -309568, -291845, -275959, -261634, -248648, -236817, -225990, -216043, -206870,
            -198380, -190499, -183161, -176309, -169896, -163878, -158218, -152884, -147847, -143081,
            -138564, -134276, -130198, -126314, -122609, -119071, -115687, -112447, -109340, -106358,
            -103493, -100736, -98082, -95523, -93054, -90670, -88365, -86135, -83977, -81885,
            -79856, -77887, -75974, -74116, -72308, -70548, -68835, -67165, -65536, -63947,
            -62395, -60880, -59398, -57950, -56532, -55144, -53784, -52451, -51145, -49863,
            -48605, -47369, -46156, -44963, -43790, -42636, -41500, -40382, -39281, -38196,
            -37126, -36071, -35030, -34002, -32988, -31986, -30996, -30018, -29050, -28093,
            -27146, -26208, -25280, -24360, -23449, -22546, -21650, -20762, -19880, -19005,
            -18136, -17273, -16416, -15564, -14717, -13874, -13036, -12202, -11372, -10545,
            -9721, -8901, -8083, -7268, -6455, -5644, -4834, -4026, -3220, -2414,
            -1609, -804, 0
        };
    }
}
